package pl.kosmowska.ewelina.client.app.activity;

import java.util.ArrayList;
import java.util.Iterator;
import java.util.List;

import pl.kosmowska.ewelina.client.ViewMessages;
import pl.kosmowska.ewelina.client.app.ClientFactory;
import pl.kosmowska.ewelina.client.app.activity.places.CategoryPlace;
import pl.kosmowska.ewelina.client.app.activity.places.SignInPlace;
import pl.kosmowska.ewelina.client.app.requestfactory.CategoryDataRequest;
import pl.kosmowska.ewelina.client.app.requestfactory.dto.CategoryDataProxy;
import pl.kosmowska.ewelina.client.app.requestfactory.dto.CategoryItemDataProxy;
import pl.kosmowska.ewelina.client.app.user.AuthEvent;
import pl.kosmowska.ewelina.client.app.user.AuthEvent.Auth;
import pl.kosmowska.ewelina.client.app.user.AuthEventHandler;
import pl.kosmowska.ewelina.client.views.CategoryView;
import pl.kosmowska.ewelina.client.views.widgets.CategoryEditItemWidget;
import pl.kosmowska.ewelina.client.views.widgets.CategoryWidget;

import com.google.gwt.activity.shared.AbstractActivity;
import com.google.gwt.event.shared.EventBus;
import com.google.gwt.place.shared.Place;
import com.google.gwt.user.client.ui.AcceptsOneWidget;
import com.google.gwt.user.client.ui.TreeItem;
import com.google.web.bindery.requestfactory.shared.Receiver;
import com.google.web.bindery.requestfactory.shared.Request;
import com.google.web.bindery.requestfactory.shared.ServerFailure;

public class CategoryActivity extends AbstractActivity implements CategoryView.Presenter{
	 
	private CategoryView view;

	  private ClientFactory clientFactory;
	  

	  public CategoryActivity(CategoryPlace place, ClientFactory clientFactory) {
	    this.clientFactory = clientFactory;
	  }


		@Override
		public void start(AcceptsOneWidget containerWidget, EventBus eventBus) {
			view = clientFactory.getCategoryView();
			view.setPresenter(this);
			initAuthorisationForView();
			startView();
			containerWidget.setWidget(view.asWidget());
		}

		private void initAuthorisationForView() {
			if (view.isAlreadyInit() == false) {
				clientFactory.getEventBus().addHandler(AuthEvent.TYPE, new AuthEventHandler() {
					public void onAuthEvent(AuthEvent event) {
						Auth e = event.getAuthEvent();
						if (e == Auth.LOGGEDIN) {
							loadCategories();
						} else if (e == Auth.LOGGEDOUT) {
							goTo(new SignInPlace());
						}
					}
				});
			}
			view.setAlreadyInit(true);
		}
		
		private void startView() {
			if (clientFactory.getIsLoggedIn() == null) {
				// wait for login event b/c hasn't happened yet
			} else if (clientFactory.getIsLoggedIn() == true) {
				loadCategories(); 
			} else if (clientFactory.getIsLoggedIn() == false) { 
				goTo(new SignInPlace());
			}
		}

	  public void goTo(Place place) {
	    clientFactory.getPlaceController().goTo(place);
	  }


	@Override
	public void loadCategories() {
		clientFactory.getAppLoadingView().startProcessing();
	    Request<List<CategoryDataProxy>> req = clientFactory.getRequestFactory().getCategoryDataRequest().findCategoryDataByUser().with("items");
	    req.fire(new Receiver<List<CategoryDataProxy>>() {
	      public void onSuccess(List<CategoryDataProxy> categoryDataList) {
	        view.initCategoryList(categoryDataList);
	        view.showCatoryTree();
			clientFactory.getAppLoadingView().stopProcessing();

	      }
	      public void onFailure(ServerFailure error) {
	        super.onFailure(error);
	        clientFactory.getAppLoadingView().stopProcessing();
	      }
	    });
		
	}

	@Override
	public void save(final TreeItem mailPanelRoot) {

		// get the requestContext
		CategoryDataRequest request = clientFactory.getRequestFactory().getCategoryDataRequest();
		CategoryDataProxy data=((CategoryWidget)mailPanelRoot.getWidget()).getData(request);
		data.setItems(getItems(mailPanelRoot,request));

		request.persist(data).with("items").fire(new Receiver<CategoryDataProxy>() {
			public void onSuccess(CategoryDataProxy categoryData) {
				CategoryWidget widget =((CategoryWidget)mailPanelRoot.getWidget());
				widget.setData(0, categoryData);
				List<CategoryItemDataProxy> list=categoryData.getItems();
				if(list!=null){
					Iterator<CategoryItemDataProxy> itr =list.iterator();
					if (!(mailPanelRoot.getChildCount()== 0)) {
						for (int i=0; i < mailPanelRoot.getChildCount(); i++) {
							CategoryEditItemWidget wItem = (CategoryEditItemWidget) mailPanelRoot.getChild(i).getWidget();		      
							wItem.setData(0, itr.next());
						}
					}
				}

			}
			public void onFailure(ServerFailure error) {
				view.showMessage(ViewMessages.ERROR_TIME_OUT);
				super.onFailure(error);
			}
		});
	}
	

	@Override
	public void removeCategoryItem(String id, final CategoryEditItemWidget categoryEditItemWidget) {
		Request<Boolean> req = clientFactory.getRequestFactory().getCategoryItemDataRequest().deleteCategoryItemData(id);
		req.fire(new Receiver<Boolean>() {
			public void onSuccess(Boolean data) {
				if (data != null && data.booleanValue() == true) {
					categoryEditItemWidget.removeFromParent();
					categoryEditItemWidget.removeFromTree();
				} else {
					view.showMessage(ViewMessages.ERROR_ON_DELETE);
				}
			}
			public void onFailure(ServerFailure error) {
				view.showMessage(ViewMessages.ERROR_ON_DELETE);
				super.onFailure(error);
			}
		});
		
	}
	
	private List<CategoryItemDataProxy> getItems(TreeItem mailPanelRoot, CategoryDataRequest request) {
		if (mailPanelRoot.getChildCount()== 0) {
			return null;
		}
		List<CategoryItemDataProxy> items = new ArrayList<CategoryItemDataProxy>();
		for (int i=0; i < mailPanelRoot.getChildCount(); i++) {
			CategoryEditItemWidget wItem = (CategoryEditItemWidget) mailPanelRoot.getChild(i).getWidget();		      
			items.add(wItem.getData(request));
		}
		return items;
	}


	@Override
	public void deleteCategory(CategoryDataProxy categoryData,
			final CategoryWidget categoryWidget) {
		Request<Boolean> req = clientFactory.getRequestFactory().getCategoryDataRequest().deleteById(categoryData.getId());
		req.fire(new Receiver<Boolean>() {
			public void onSuccess(Boolean data) {
				if (data != null && data.booleanValue() == true) {
					categoryWidget.removeFromParent();
					categoryWidget.removeFromTree();
				} else {
					view.showMessage(ViewMessages.ERROR_ON_DELETE);
				}
			}
			public void onFailure(ServerFailure error) {
				view.showMessage(ViewMessages.ERROR_ON_DELETE);
				super.onFailure(error);
			}
		});
		
	}


}
